package com.gjy.sentinel.annotation.aspect;

import com.alibaba.csp.sentinel.context.ContextUtil;
import com.gjy.sentinel.annotation.SentinelOrigin;
import org.aspectj.lang.ProceedingJoinPoint;
import org.aspectj.lang.annotation.Around;
import org.aspectj.lang.annotation.Aspect;
import org.aspectj.lang.annotation.Pointcut;
import org.springframework.core.annotation.Order;
import org.springframework.stereotype.Component;

/**
 * 在所有标有 @SentinelOrigin 的方法执行前，先把 origin 写入 Sentinel Context。
 * <p>
 * 确保该切面在 Sentinel 的内部拦截器（SentinelResourceAspect）**之前**执行。
 */
@Aspect
@Order(0)   // 必须比 SentinelResourceAspect 的 order 更小
@Component
public class SentinelOriginAspect {

    @Pointcut("@annotation(sentinelOrigin)")
    public void sentinelOriginPointcut(SentinelOrigin sentinelOrigin) {
    }

    @Around(value = "sentinelOriginPointcut(sentinelOrigin)", argNames = "pjp,sentinelOrigin")
    public Object around(ProceedingJoinPoint pjp, SentinelOrigin sentinelOrigin) throws Throwable {
        // 这里的 resourceName 可以随意取，只是为了在 Dashboard 中区分不同入口
        ContextUtil.enter(sentinelOrigin.resourceName(), sentinelOrigin.value());
        try {
            return pjp.proceed();
        } finally {
            ContextUtil.exit();
        }
    }

}
